package com.campus.customer.controller;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.util.RandomUtil;
import cn.hutool.json.JSONUtil;
import com.campus.common.bean.common.Pagination;
import com.campus.common.bean.common.Resp;
import com.campus.common.enums.DeliveryTypeEnum;
import com.campus.common.enums.OrderStatusEnum;
import com.campus.common.exception.BusinessException;
import com.campus.customer.bean.order.OrderGoodsBean;
import com.campus.customer.bean.order.OrderQueryParam;
import com.campus.customer.bean.order.OrderSubmitBean;
import com.campus.customer.dto.*;
import com.campus.customer.entity.Merchant;
import com.campus.customer.entity.Order;
import com.campus.customer.entity.OrderGoods;
import com.campus.customer.entity.User;
import com.campus.customer.feign.PaymentFeignClient;
import com.campus.customer.service.*;
import com.campus.customer.vo.UserInfoVo;
import com.campus.customer.vo.order.OrderStatusCountVo;
import com.campus.customer.vo.order.OrderVo;
import com.github.pagehelper.PageInfo;
import com.google.common.collect.Lists;
import com.wechat.pay.java.service.partnerpayments.jsapi.model.Transaction;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.*;

import java.math.BigDecimal;
import java.time.LocalDateTime;
import java.util.List;
import java.util.stream.Collectors;

/**
 * <p>
 * 订单表 前端控制器
 * </p>
 *
 * @author ZhaoYuJie
 * @since 2025-04-02
 */
@RestController
@RequestMapping("/order")
@Api(tags = "订单管理")
@Slf4j
public class OrderController {

    @Autowired
    private OrderService orderService;
    @Autowired
    private MerchantService merchantService;
    @Autowired
    private SessionService sessionService;
    @Autowired
    private OrderGoodsService orderGoodsService;
    @Autowired
    private OrderTimeoutService orderTimeoutService;
    @Autowired
    private UserService userService;
    @Autowired
    private PaymentFeignClient paymentFeignClient;
    @Autowired
    private KafkaProducerService kafkaProducerService;


    @PostMapping("/submit")
    @ApiOperation("提交订单，返回订单ID")
    public Resp<String> submitOrder(@RequestBody OrderSubmitBean orderSubmitBean) {
        // 获取当前用户信息
        UserInfoVo userInfo = sessionService.getUserInfo();
        // 创建订单实体
        Order order = new Order();
        BeanUtil.copyProperties(orderSubmitBean, order);
        // 如果是外卖配送，则保存配送时间相关信息
        if (DeliveryTypeEnum.TAKEOUT.getValue() == orderSubmitBean.getDeliveryType()) {
            order.setDeliveryTimeType(orderSubmitBean.getDeliveryTimeType());
            order.setScheduleTime(orderSubmitBean.getScheduleTime());
        }
        String flag = DeliveryTypeEnum.getByValue(orderSubmitBean.getDeliveryType()).getFlag();
        String orderId = flag
                + System.currentTimeMillis()
                + String.format("%03d", userInfo.getId() % 1000)
                + String.format("%03d", RandomUtil.randomInt(1000)); // 改为3位随机数
        order.setId(orderId);
        order.setUserId(userInfo.getId());
        order.setCustomerPhone(userInfo.getPhone());

        Merchant merchant = merchantService.getById(orderSubmitBean.getMerchantId());
        order.setMerchantPhone(merchant.getPhone());

        order.setStatus(OrderStatusEnum.PENDING_PAYMENT.getValue()); // 假设初始状态为待付款
        order.setStatusText(OrderStatusEnum.PENDING_PAYMENT.getText());

        // 创建订单商品实体
        List<OrderGoods> orderGoodsList = Lists.newArrayList();
        List<OrderGoodsBean> orderGoodsBeanList = orderSubmitBean.getGoods();
        for (OrderGoodsBean orderGoodsBean : orderGoodsBeanList) {
            OrderGoods orderGoods = new OrderGoods();
            orderGoods.setGoodsId(orderGoodsBean.getId());
            orderGoods.setName(orderGoodsBean.getName());
            orderGoods.setPrice(orderGoodsBean.getPrice());
            orderGoods.setImage(orderGoodsBean.getImage());
            // 转换 specifications
            orderGoods.setSpecifications(JSONUtil.toJsonStr(orderGoodsBean.getSpecifications()));
            orderGoods.setQuantity(orderGoodsBean.getQuantity());
            orderGoods.setSubtotal(orderGoodsBean.getPrice().multiply(BigDecimal.valueOf(orderGoodsBean.getQuantity())));
            orderGoodsList.add(orderGoods);
        }
        orderService.createOrder(order, orderGoodsList);
        
        // 添加订单到超时队列
        orderTimeoutService.addOrderToTimeoutQueue(orderId);

        return Resp.success(orderId);
    }

    @PostMapping("/pay/{orderId}")
    @ApiOperation("创建微信支付订单")
    public Resp<PayOrderResponseDTO> createPayOrder(@PathVariable String orderId) {
        try {
            // 获取订单信息
            Order order = orderService.getById(orderId);
            if (order == null) {
                return Resp.error("订单不存在");
            }
            
            // 检查订单状态
            if (OrderStatusEnum.PENDING_PAYMENT.getValue() != order.getStatus()) {
                return Resp.error("订单状态不正确，无法支付");
            }
            
            // 获取商户信息
            Merchant merchant = merchantService.getById(order.getMerchantId());
            if (merchant == null) {
                return Resp.error("商户不存在");
            }
            
            // 获取用户信息
            UserInfoVo userInfo = sessionService.getUserInfo();
            User user = userService.getById(userInfo.getId());
            if (user == null) {
                return Resp.error("用户不存在");
            }
            
            // 获取订单商品信息
            List<OrderGoods> orderGoodsList = orderGoodsService.getOrderGoodsByOrderId(order.getId());
            
            // 构造支付请求
            PayOrderRequestDTO payRequest = new PayOrderRequestDTO();
            payRequest.setOrderId(order.getId());
            payRequest.setUserId(user.getId());
            payRequest.setUserOpenid(user.getOpenid());
            payRequest.setMerchantId(merchant.getId());
            payRequest.setSubMchid(merchant.getSubMchid());
            payRequest.setActualPay(order.getActualPay());
            
            // 转换订单商品信息
            List<PayOrderRequestDTO.OrderGoodsDTO> orderGoodsDTOs = orderGoodsList.stream()
                    .map(goods -> {
                        PayOrderRequestDTO.OrderGoodsDTO dto = new PayOrderRequestDTO.OrderGoodsDTO();
                        dto.setName(goods.getName());
                        dto.setPrice(goods.getPrice());
                        dto.setQuantity(goods.getQuantity());
                        return dto;
                    })
                    .collect(Collectors.toList());
            payRequest.setOrderGoods(orderGoodsDTOs);
            
            // 调用支付服务
            Resp<PayOrderResponseDTO> payResponse = paymentFeignClient.createPayOrder(payRequest);
            
            if ("0".equals(payResponse.getCode())) {
                return Resp.success(payResponse.getData());
            } else {
                return Resp.error(payResponse.getMessage());
            }
        } catch (Exception e) {
            log.error("创建支付订单失败", e);
            return Resp.error("创建支付订单失败: " + e.getMessage());
        }
    }

    @GetMapping("/detail/{orderId}")
    @ApiOperation("获取订单详情")
    public Resp<OrderVo> getOrderDetail(@PathVariable String orderId) {
        Order order = orderService.getById(orderId);
        if (order == null) {
            return Resp.error("订单不存在");
        }
        OrderVo orderVo = new OrderVo();
        BeanUtil.copyProperties(order, orderVo);
        orderVo.setGoods(orderGoodsService.getOrderGoodsByOrderId(order.getId()));
        return Resp.success(orderVo);
    }

    @ApiOperation("分页查询订单列表")
    @GetMapping("/page")
    public Resp<Pagination<OrderVo>> page(OrderQueryParam param) {
        UserInfoVo userInfo = sessionService.getUserInfo();
        param.setUserId(userInfo.getId());
        PageInfo<OrderVo> pageInfo = orderService.getOrderVoPage(param);
        return Resp.successPageable(pageInfo);
    }

    @PostMapping("/cancel/{orderId}")
    @ApiOperation("取消订单")
    public Resp<String> cancelOrder(@PathVariable String orderId, @RequestBody CancelOrderRequestDTO request) {
        // 直接调用Service层的取消订单方法，传递取消原因
        boolean success = orderService.cancelOrder(orderId, request.getCancelReason());
        if (success) {
            return Resp.success("订单取消成功");
        } else {
            return Resp.error("订单取消失败");
        }
    }

    @GetMapping("/getOrderStatusCountList")
    @ApiOperation("查询订单各状态和对应数量")
    public Resp<List<OrderStatusCountVo>> getOrderStatusCountList() {
        Integer userId = sessionService.getUserInfo().getId();
        return Resp.success(orderService.getOrderStatusCountList(userId));
    }

    @PostMapping("/updatePaymentStatus")
    @ApiOperation("更新订单支付状态")
    public Resp<String> updatePaymentStatus(@RequestBody OrderStatusUpdateDTO request) {
        log.info("更新订单支付状态，订单号：{}", request.getOrderId());
        try {
            // 根据订单号查询订单
            Order order = orderService.getById(request.getOrderId());
            if (order == null) {
                return Resp.error("订单不存在");
            }
            
            // 检查订单状态是否为待支付
            if (OrderStatusEnum.PENDING_PAYMENT.getValue() != order.getStatus()) {
                return Resp.error("订单状态不正确，无法更新支付状态");
            }
            
            // 更新订单状态
            order.setStatus(request.getStatus());
            order.setStatusText(request.getStatusText());
            order.setPayTime(request.getPayTime());
            order.setTransactionId(request.getTransactionId());
            orderService.updateById(order);
            
            // 从超时队列中移除订单
            orderTimeoutService.removeOrderFromTimeoutQueue(request.getOrderId());
            
            // 发送新订单通知（这里需要注入KafkaProducerService）
             kafkaProducerService.sendNewOrderMessage(order.getId(), order.getMerchantId());
            
            log.info("订单支付状态更新成功，订单号: {}，微信支付订单号: {}", request.getOrderId(), request.getTransactionId());
            return Resp.success("订单支付状态更新成功");
        } catch (Exception e) {
            log.error("更新订单支付状态失败，订单号: {}", request.getOrderId(), e);
            return Resp.error("更新订单支付状态失败: " + e.getMessage());
        }
    }

    @PostMapping("/refreshPaymentStatus/{orderId}")
    @ApiOperation("刷新微信支付状态")
    public Resp<OrderVo> refreshPaymentStatus(@PathVariable String orderId) {
        log.info("刷新微信支付状态，订单号：{}", orderId);
        try {
            // 获取订单信息
            Order order = orderService.getById(orderId);
            if (order == null) {
                return Resp.error("订单不存在");
            }
            
            // 只有待支付状态的订单才需要刷新支付状态
            if (OrderStatusEnum.PENDING_PAYMENT.getValue() != order.getStatus()) {
                log.info("订单{}状态为{}，无需刷新支付状态", orderId, order.getStatusText());
                return getOrderDetail(orderId);
            }
            
            // 获取商户信息
            Merchant merchant = merchantService.getById(order.getMerchantId());
            if (merchant == null) {
                return Resp.error("商户不存在");
            }
            
            // 构造查询请求
            OrderStatusQueryDTO queryRequest = new OrderStatusQueryDTO();
            queryRequest.setOutTradeNo(orderId);
            queryRequest.setSubMchid(merchant.getSubMchid());
            
            // 调用支付服务查询订单详情
            Resp<Transaction> queryResponse =
                    paymentFeignClient.queryOrderDetail(queryRequest);
            
            if (!Resp.CODE_SUCCESS.equals(queryResponse.getCode())) {
                log.error("查询微信支付订单详情失败：{}", queryResponse.getMessage());
                return getOrderDetail(orderId);
            }
            
            Transaction transaction = queryResponse.getData();
            if (transaction == null) {
                log.error("微信支付订单详情为空");
                return getOrderDetail(orderId);
            }
            
            // 判断支付状态
            if ("SUCCESS".equals(transaction.getTradeState().name())) {
                // 支付成功，更新订单状态
                OrderStatusUpdateDTO updateRequest = new OrderStatusUpdateDTO();
                updateRequest.setOrderId(orderId);
                updateRequest.setTransactionId(transaction.getTransactionId());
                updateRequest.setPayTime(LocalDateTime.now());
                updateRequest.setStatus(OrderStatusEnum.PENDING_ACCEPTANCE.getValue());
                updateRequest.setStatusText(OrderStatusEnum.PENDING_ACCEPTANCE.getText());
                
                // 调用自身的更新支付状态方法
                Resp<String> updateResult = updatePaymentStatus(updateRequest);
                if (!Resp.CODE_SUCCESS.equals(updateResult.getCode())) {
                    log.error("更新订单支付状态失败：{}", updateResult.getMessage());
                }
                
                log.info("订单{}支付状态刷新成功，已更新为待接单状态", orderId);
            } else {
                log.info("订单{}微信支付状态为{}，暂未支付成功", orderId, transaction.getTradeState().name());
            }
            
            // 返回最新的订单详情
            return getOrderDetail(orderId);
            
        } catch (Exception e) {
            log.error("刷新微信支付状态失败，订单号: {}", orderId, e);
            return Resp.error("刷新微信支付状态失败: " + e.getMessage());
        }
    }


}